package com.xplay.xpocker.message.connecter;

import com.xplay.xpocker.business.BusinessEnum;
import com.xplay.xpocker.business.BusinessException;
import com.xplay.xpocker.entity.mahjong.MahjongRoomBuilder;
import com.xplay.xpocker.entity.mahjong.MahjongUserTask;
import com.xplay.xpocker.meta.MessageContent;
import com.xplay.xpocker.meta.realize.MahjongRoomEntity;
import com.xplay.xpocker.meta.realize.MahjongUserChannel;
import com.xplay.xpocker.meta.room.MetaRoomEntity;
import com.xplay.xpocker.meta.user.MetaUserChannel;
import com.xplay.xpocker.observer.SubscriptionSubject;
import com.xplay.xpocker.service.mahjong.IDiskPartService;
import com.xplay.xpocker.service.mahjong.IRoomService;
import com.xplay.xpocker.socket.UserChannelMate;
import com.xplay.xpocker.util.BusinessAssertion;
import com.xplay.xpocker.util.DictionaryConst;
import com.xplay.xpocker.util.SpringContextHolder;
import io.netty.channel.ChannelHandlerContext;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.locks.ReentrantLock;

import static com.xplay.xpocker.util.DictionaryConst.MahjongAction.READ_HOME;
import static com.xplay.xpocker.util.DictionaryConst.MahjongAction.USER_PREPARE;

/**
 * @author wanjie
 * @date 2021/3/17 21:42
 */

public abstract class ConnectStrategy implements UserChannelMate {
    public abstract MetaRoomEntity doOneMoreThing(ChannelHandlerContext ctx, MetaRoomEntity roomInfo, boolean firstConnection);

    public void doConnect(ChannelHandlerContext ctx, String roomCode) {
        IRoomService roomService = SpringContextHolder.getBean(IRoomService.class);
        try {
            MetaRoomEntity roomInfo = roomService.queryRoomInfo(roomCode);
            BusinessAssertion.isNull(BusinessEnum.ROOM_NOT_FOUND, roomInfo);
            SubscriptionSubject subject = null;
            boolean isNewUser = false;
            subject = diskPart.get(roomCode);
            if (subject == null) {
                subject = new SubscriptionSubject();
                diskPart.put(roomCode, subject);
            }
            HashMap<String, MetaUserChannel> userChannelHashMap = roomInfo.getAllUserInfo();
            BusinessAssertion.isTrue(BusinessEnum.ROOM_NOT_FOUND, userChannelHashMap == null);
            log.info(String.format("========加入房间============== room [%s] ===========user [%s]======", roomCode, getUserId(ctx)));
            MetaUserChannel menUser = userChannelHashMap.get(getUserId(ctx));
            if (menUser == null) {
                menUser = (MetaUserChannel) roomService.addRoom(roomCode, getUserId(ctx)).getAllUserInfo().get(getUserId(ctx));
            }
            BusinessAssertion.isNull(BusinessEnum.ROOM_FULL, menUser);
            if (!menUser.isFirstConnection()) {
                isNewUser = true;
                menUser.setFirstConnection(true);
            }
            menUser.setOnline(true);
            menUser.setUserCtx(ctx);
            menUser.setChannel(ctx);
            subject.attach(menUser);
            /**
             * 当连接成功 内部做完其它事情后 这里就需要将房间类型转为子类型了
             */
            roomService.saveRoomInfo(doOneMoreThing(ctx, roomInfo, isNewUser));
        } catch (BusinessException e) {
            e.printStackTrace();
            throw e;
        }
    }
}
